package com.fy.fyspace.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.fy.fyspace.common.result.PageResult;
import com.fy.fyspace.common.result.R;
import com.fy.fyspace.constant.ResultMessageConstant;
import com.fy.fyspace.ex.ConditionException;
import com.fy.fyspace.mapper.PictureMapper;
import com.fy.fyspace.model.dto.picture.*;
import com.fy.fyspace.model.entity.Picture;
import com.fy.fyspace.model.enums.picture.PictureDeleteStatusEnum;
import com.fy.fyspace.model.enums.picture.PictureReviewStatusEnum;
import com.fy.fyspace.model.vo.picture.ReviewPictureVO;
import com.fy.fyspace.service.ReviewService;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.http.HttpSession;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import static com.fy.fyspace.common.result.R.ok;

/**
 * 图片审核服务实现类
 */
@Service
@Slf4j
public class ReviewServiceImpl implements ReviewService {

    @Resource
    private PictureMapper pictureMapper;

    @Resource
    private RedisTemplate<String, Object> redisTemplate;

    private static final String PICTURE_STATISTICS_CACHE_KEY = "picture:statistics";
    private static final String PICTURE_CATEGORIES_CACHE_KEY = "picture:categories";
    private static final String PICTURE_TAGS_CACHE_KEY = "picture:tags";

    /**
     * 获取图片列表
     * @param page        页码
     * @param pageSize    每页数量
     * @param searchText  搜索关键词
     * @param status      审核状态
     * @param startTime   开始时间
     * @param endTime     结束时间
     * @param httpSession 会话信息
     * @return
     */
    @Override
    public R getPictureList(Integer page, Integer pageSize, String searchText,
                                 String status, String startTime, String endTime, HttpSession httpSession) {
        log.info("开始获取图片列表: page={}, pageSize={}, searchText={}, status={}, startTime={}, endTime={}",
                page, pageSize, searchText, status, startTime, endTime);

        try {
            page = page == null ? 1 : page;
            pageSize = pageSize == null ? 35 : pageSize;
            // 构建查询条件
            LambdaQueryWrapper<Picture> queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(Picture::getIsDelete, 0);

            // 根据状态查询
            if (StrUtil.isNotBlank(status)) {
                if ("通过".equals(status)) {
                    queryWrapper.eq(Picture::getReviewStatus, PictureReviewStatusEnum.PASS.getValue());
                } else if ("拒绝".equals(status)) {
                    queryWrapper.eq(Picture::getReviewStatus, PictureReviewStatusEnum.REJECT.getValue());
                } else if ("待审核".equals(status)) {
                    queryWrapper.eq(Picture::getReviewStatus, PictureReviewStatusEnum.REVIEWING.getValue());
                }
            }

            // 添加时间范围条件
            if (StrUtil.isNotBlank(startTime)) {
                queryWrapper.ge(Picture::getCreateTime, DateUtil.parse(startTime));
            }
            if (StrUtil.isNotBlank(endTime)) {
                queryWrapper.le(Picture::getCreateTime, DateUtil.parse(endTime));
            }

            // 添加搜索条件
            if (StrUtil.isNotBlank(searchText)) {
                queryWrapper.and(wrapper -> wrapper
                        .like(Picture::getName, searchText)
                        .or()
                        .like(Picture::getIntroduction, searchText));
            }

            // 按创建时间倒序排序
            queryWrapper.orderByDesc(Picture::getCreateTime);

            // 在执行查询前添加分页设置
            PageHelper.startPage(page, pageSize);

            // 执行查询
            List<Picture> pictureList = pictureMapper.selectList(queryWrapper);
            // 获取分页信息
            PageInfo<Picture> pageInfo = new PageInfo<>(pictureList);
            log.info("分页查询结果 - 当前页：{}，每页数量：{}，总记录数：{}，总页数：{}",
                    pageInfo.getPageNum(), pageInfo.getPageSize(),
                    pageInfo.getTotal(), pageInfo.getPages());

            List<ReviewPictureVO> pictureVOList = pictureList.stream()
                    .map(p -> {
                        ReviewPictureVO vo = BeanUtil.copyProperties(p, ReviewPictureVO.class);
                        vo.setId(p.getId() != null ? String.valueOf(p.getId()) : null);
                        return vo;
                    })
                    .collect(Collectors.toList());

            PageResult<ReviewPictureVO> pageResult = new PageResult<>();
            pageResult.setList(pictureVOList);
            pageResult.setPageNo(Long.valueOf(pageInfo.getPageNum()));
            pageResult.setPageSize(Long.valueOf(pageInfo.getPageSize()));
            pageResult.setTotalCount(pageInfo.getTotal());
            pageResult.setPageTotal(Long.valueOf(pageInfo.getPages()));

            return ok(pageResult);
        } catch (Exception e) {
            log.error("获取图片列表失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 获取图片统计数据
     *
     * @return
     */
@Override
public R getStatistics() {
    // 1. 查询待审核数量
    LambdaQueryWrapper<Picture> pendingWrapper = new LambdaQueryWrapper<>();
    pendingWrapper.eq(Picture::getIsDelete, PictureDeleteStatusEnum.NOT_DELETE.getValue())
            .eq(Picture::getReviewStatus, PictureReviewStatusEnum.REVIEWING.getValue());
    long pendingCount = pictureMapper.selectCount(pendingWrapper);

    // 2. 查询今日已审核数量（无论通过还是拒绝，只要reviewTime在今天范围内）
    Date todayStart = DateUtil.beginOfDay(new Date());
    Date todayEnd = DateUtil.endOfDay(new Date());
    LambdaQueryWrapper<Picture> todayReviewedWrapper = new LambdaQueryWrapper<>();
    todayReviewedWrapper.eq(Picture::getIsDelete, PictureDeleteStatusEnum.NOT_DELETE.getValue())
            .isNotNull(Picture::getReviewTime)
            .ge(Picture::getReviewTime, todayStart)
            .le(Picture::getReviewTime, todayEnd);
    long todayApprovedCount = pictureMapper.selectCount(todayReviewedWrapper);

    // 3. 查询累计违规数量（所有未删除且被拒绝的图片）
    LambdaQueryWrapper<Picture> violationWrapper = new LambdaQueryWrapper<>();
    violationWrapper.eq(Picture::getIsDelete, PictureDeleteStatusEnum.NOT_DELETE.getValue())
            .eq(Picture::getReviewStatus, PictureReviewStatusEnum.REJECT.getValue());
    long violationCount = pictureMapper.selectCount(violationWrapper);

    // 4. 查询总图片数量
    LambdaQueryWrapper<Picture> totalWrapper = new LambdaQueryWrapper<>();
    totalWrapper.eq(Picture::getIsDelete, PictureDeleteStatusEnum.NOT_DELETE.getValue());
    long totalCount = pictureMapper.selectCount(totalWrapper);

    // 返回结果
    Map<String, Object> resultMap = new HashMap<>();
    resultMap.put("todayApprovedCount", todayApprovedCount);
    resultMap.put("totalCount", totalCount);
    resultMap.put("pendingCount", pendingCount);
    resultMap.put("violationCount", violationCount);
    return ok(resultMap);
}

    /**
     * 批量审核通过图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R batchApprovePictures(PictureBatchApproveDTO request) {
        try {
            log.info("开始批量审核通过图片: pictureIds={}", request.getPictureIds());

            if (request.getPictureIds() == null || request.getPictureIds().isEmpty()) {
                log.warn("批量审核失败：图片ID列表为空");
                throw new ConditionException("请选择要审核的图片");
            }

            // 批量更新图片状态
            List<Picture> pictures = pictureMapper.selectBatchIds(request.getPictureIds());
            if (pictures.isEmpty()) {
                log.warn("批量审核失败：未找到指定的图片");
                throw new ConditionException("未找到指定的图片");
            }

            Date now = new Date();
            for (Picture picture : pictures) {
                picture.setReviewStatus(PictureReviewStatusEnum.PASS.getValue());
                picture.setReviewTime(now);
                picture.setUpdateTime(now);
                pictureMapper.updateById(picture);
            }

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("批量审核通过完成: count={}", pictures.size());
            return ok("审核成功");
        } catch (Exception e) {
            log.error("批量审核通过图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 审核通过单张图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R approvePicture(Long pictureId, Long userId) {
        try {
            log.info("开始审核通过单张图片: pictureId={}", pictureId);

            Picture picture = pictureMapper.selectById(pictureId);
            if (picture == null) {
                log.warn("审核失败：未找到指定的图片 pictureId={}", pictureId);
                throw new ConditionException("未找到指定的图片");
            }

            Date now = new Date();
            picture.setReviewStatus(PictureReviewStatusEnum.PASS.getValue());
            picture.setReviewerId(userId);
            picture.setReviewTime(now);
            picture.setUpdateTime(now);
            pictureMapper.updateById(picture);

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("审核通过完成: pictureId={}", pictureId);
            return ok("审核成功");
        } catch (Exception e) {
            log.error("审核通过单张图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 拒绝单张图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R rejectPicture(Long pictureId, PictureRejectDTO request) {
        try {
            log.info("开始拒绝单张图片: pictureId={}, reason={}, comment={}",
                    pictureId, request.getReason(), request.getReviewMessage());

            if (request.getReason()==null) {
                log.warn("拒绝失败：未提供拒绝原因");
                throw new ConditionException("请提供拒绝原因");
            }

            Picture picture = pictureMapper.selectById(pictureId);
            if (picture == null) {
                log.warn("拒绝失败：未找到指定的图片 pictureId={}", pictureId);
                throw new ConditionException("未找到指定的图片");
            }

            Date now = new Date();
            picture.setReviewStatus(PictureReviewStatusEnum.REJECT.getValue());
            picture.setReviewMessage(request.getReviewMessage());
            picture.setRejectType(request.getReason());
            picture.setReviewTime(now);
            picture.setUpdateTime(now);
            pictureMapper.updateById(picture);

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("拒绝完成: pictureId={}", pictureId);
            return ok("操作成功");
        } catch (Exception e) {
            log.error("拒绝单张图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 批量拒绝图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R batchRejectPictures(PictureBatchRejectDTO request) {
        try {
            log.info("开始批量拒绝图片: pictureIds={}, type={}, message={}",
                    request.getPictureIds(), request.getRejectType(), request.getReviewMessage());

            if (request.getPictureIds() == null || request.getPictureIds().isEmpty()) {
                log.warn("批量拒绝失败：图片ID列表为空");
                throw new ConditionException("请选择要拒绝的图片");
            }

            if (request.getRejectType()==null) {
                log.warn("批量拒绝失败：未提供拒绝原因");
                throw new ConditionException("请提供拒绝原因");
            }

            // 批量更新图片状态
            List<Picture> pictures = pictureMapper.selectBatchIds(request.getPictureIds());
            if (pictures.isEmpty()) {
                log.warn("批量拒绝失败：未找到指定的图片");
                throw new ConditionException("未找到指定的图片");
            }

            Date now = new Date();
            for (Picture picture : pictures) {
                picture.setReviewStatus(PictureReviewStatusEnum.REJECT.getValue());
                picture.setReviewMessage(request.getReviewMessage());
                picture.setRejectType(request.getRejectType());
                picture.setReviewTime(now);
                picture.setUpdateTime(now);
                pictureMapper.updateById(picture);
            }

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("批量拒绝完成: count={}", pictures.size());
            return ok("操作成功");
        } catch (Exception e) {
            log.error("批量拒绝图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 更新图片信息
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R updatePicture(Long pictureId, PictureUpdateDTO request) {
        try {
            log.info("开始更新图片信息: pictureId={}, request={}", pictureId, request);

            Picture picture = pictureMapper.selectById(pictureId);
            if (picture == null) {
                log.warn("更新图片信息失败：未找到指定的图片 pictureId={}", pictureId);
                throw new ConditionException("未找到指定的图片");
            }

            // 更新基本信息
            if (StrUtil.isNotBlank(request.getName())) {
                picture.setName(request.getName());
            }
            if (StrUtil.isNotBlank(request.getDescription())) {
                picture.setIntroduction(request.getDescription());
            }
            if (StrUtil.isNotBlank(request.getCategory())) {
                picture.setCategory(request.getCategory());
            }
            if (request.getTags() != null && !request.getTags().isEmpty()) {
                picture.setTagsList(request.getTags());
            }

            picture.setUpdateTime(new Date());
            pictureMapper.updateById(picture);

            // 删除相关缓存
            if (StrUtil.isNotBlank(request.getCategory())) {
                redisTemplate.delete(PICTURE_CATEGORIES_CACHE_KEY);
            }
            if (request.getTags() != null && !request.getTags().isEmpty()) {
                redisTemplate.delete(PICTURE_TAGS_CACHE_KEY);
            }

            log.info("更新图片信息成功: pictureId={}", pictureId);
            return ok("更新成功");
        } catch (Exception e) {
            log.error("更新图片信息失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 删除单张图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R deletePicture(Long pictureId) {
        try {
            log.info("开始删除单张图片: pictureId={}", pictureId);

            Picture picture = pictureMapper.selectById(pictureId);
            if (picture == null) {
                log.warn("删除图片失败：未找到指定的图片 pictureId={}", pictureId);
                throw new ConditionException("未找到指定的图片");
            }

            // 逻辑删除
            picture.setIsDelete(1);
            picture.setUpdateTime(new Date());
            pictureMapper.updateById(picture);

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("删除图片成功: pictureId={}", pictureId);
            return ok("删除成功");
        } catch (Exception e) {
            log.error("删除图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

    /**
     * 批量删除图片
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public R batchDeletePictures(PictureBatchDeleteDTO request) {
        try {
            log.info("开始批量删除图片: pictureIds={}", request.getPictureIds());

            if (request.getPictureIds() == null || request.getPictureIds().isEmpty()) {
                log.warn("批量删除失败：图片ID列表为空");
                throw new ConditionException("请选择要删除的图片");
            }

            // 批量更新图片状态
            List<Picture> pictures = pictureMapper.selectBatchIds(request.getPictureIds());
            if (pictures.isEmpty()) {
                log.warn("批量删除失败：未找到指定的图片");
                throw new ConditionException("未找到指定的图片");
            }

            Date now = new Date();
            for (Picture picture : pictures) {
                picture.setIsDelete(1);
                picture.setUpdateTime(now);
                pictureMapper.updateById(picture);
            }

            // 删除统计数据缓存
            redisTemplate.delete(PICTURE_STATISTICS_CACHE_KEY);
            log.info("批量删除完成: count={}", pictures.size());
            return ok("删除成功");
        } catch (Exception e) {
            log.error("批量删除图片失败", e);
            throw new ConditionException(ResultMessageConstant.OPERATION_ERROR);
        }
    }

}